Skip to main content
Version: 1.0.0

六、API 参考

6.1 tasys 接口详解

6.1.1 taco_sys_set_config

描述

设置公共缓存池方案。

语法

taco_s32 taco_sys_set_config(const taco_config_t *taco_config);

参数说明

参数名称描述输入/输出
taco_config指向公共缓存池方案结构体的指针输入

返回值

返回值描述
0成功设置公共缓存池方案
非 0设置失败

注意事项

  • 支持在多个进程中调用,仅限于首次调用时执行功能,后续调用直接返回失败
  • 执行模块反初始化后,已设置的公共缓存池方案同时销毁,下次初始化前需要重新设置

6.1.2 taco_sys_get_config

描述

获取已设置的公共缓存池方案。

语法

taco_s32 taco_sys_get_config(taco_config_t *taco_config);

参数说明

参数名称描述输入/输出
taco_config指向存储公共缓存池配置的结构体指针输出

返回值

返回值描述
0成功获取公共缓存池方案
非 0获取失败

注意事项

  • 该函数用于获取之前通过 taco_sys_set_config 设置的公共缓存池配置信息
  • 需要确保传入的 taco_config 指针指向有效的内存区域,函数会将获取到的配置信息填充到该结构体中
  • 只有在成功调用 taco_sys_set_config 后,才能通过此函数获取到有效的配置信息

6.1.3 taco_sys_create_pool

描述

创建一个缓存池。

详情 创建一个缓存池,常用于为特定的业务提供专用缓存,以保证服务质量(QoS)。

语法

taco_pool_t taco_sys_create_pool(const taco_pool_config_t *pool_cfg);

参数说明

参数名称描述输入/输出
pool_cfg缓存池配置输入

返回值

返回值描述
大于等于 0 的整数成功,返回值即为 pool_id
TACO_INVALID_POOLID失败

注意事项

  • 本接口创建的缓存池与公共缓存池的区别在于:
    • 公共缓存池方案可一次创建多个缓存池,而此接口每次调用只创建一个缓存池
    • 公共缓存池是必须创建的,而此接口是可选的,按需创建

6.1.4 taco_sys_destroy_pool

描述

销毁指定的缓存池。

语法

taco_s32 taco_sys_destroy_pool(taco_pool_t pool);

参数说明

参数名称描述输入/输出
pool创建的缓存池 ID输入

返回值

返回值描述
0成功
非 0失败

注意事项

  • 本接口只用于销毁使用 taco_sys_create_pool 接口创建的缓存池

6.1.5 taco_sys_get_block

描述

从公共缓存池或指定缓存池中申请一个缓存块,并获得该缓存块的 VBID(Virtual Block ID)。

语法

taco_blk_t taco_sys_get_block(
taco_pool_t pool,
taco_u64 blk_size,
const taco_char *zone_name
);

参数说明

参数名称描述输入/输出
pool缓存池 ID。 - 若想从公共缓存池中获取 VB,则传入特殊值 TACO_INVALID_POOLID - 若想从特定的 pool 中获取 VB,则传入一个有效的 pool_id输入
blk_size需要从缓存池中获取的 VB 的大小(以字节为单位)输入
zone_nameZone 名称。 - 若为 NULL,则在默认的 zone 上按规则获取 VB - 若非 NULL,则在指定的 zone 上按规则获取 VB输入

返回值

返回值描述
0失败
非 0所分配缓存块的 block ID

6.1.6 taco_sys_get_block_size

描述

获取一个缓存块的容量。

语法

taco_s32 taco_sys_get_block_size(
taco_pool_t pool,
taco_blk_t block,
taco_u64 *get_size
);

参数说明

参数名称描述输入/输出
pool缓存池 ID输入
blockVB 块的 ID输入
get_size指向存储块大小的指针变量,用于输出获取到的块大小输出

返回值

返回值描述
0成功获取缓存块大小
非 0获取失败

注意事项

  • 此函数用于查询已分配缓存块的实际大小,可用于验证分配的内存块是否符合预期
  • 需要传入有效的 poolblock 参数才能正确获取块大小
  • get_size 参数必须指向一个有效的内存地址,函数会将获取到的块大小写入该地址指向的变量中
  • 在调用此函数前,确保对应的缓存块仍然有效且未被释放

6.1.7 taco_sys_release_block

描述

释放一个缓存块。

详情

将缓存块归还给所属的 pool,以便循环使用。

语法

taco_s32 taco_sys_release_block(taco_blk_t block);

参数说明

参数名称描述输入/输出
block要释放的 VB 的 ID输入

返回值

返回值描述
0成功
非 0失败

注意事项

  • 在释放缓存块之前,必须确保已经解除所有虚拟地址映射关系
  • 释放后的缓存块可以被其他请求重新分配使用

6.1.8 taco_sys_handle2_phys_addr

描述

获取一个缓存块的物理地址。

语法

taco_u64 taco_sys_handle2_phys_addr(taco_blk_t block);

参数说明

参数名称描述输入/输出
block需要获取的 VB 的 ID输入

返回值

返回值描述
非 0成功
0失败

注意事项

  • 该函数返回的是缓存块在物理内存中的起始地址
  • 物理地址可以直接用于硬件访问

6.1.9 taco_sys_handle2_meta_addr

描述

获取一个缓存块的元数据的物理地址。

详情

每个 VB 缓存块都自动关联一个元数据(metadata),其大小在创建 pool 时指定(大小可以为 0)。本接口用于获取元数据的物理地址。

语法

taco_u64 taco_sys_handle2_meta_addr(taco_blk_t block);

参数说明

参数名称描述输入/输出
block目标 VB 的 ID输入

返回值

返回值描述
非 0成功
0失败

注意事项

  • VB 元数据的生命周期与 VB 本身相同,所以 SDK 内部处理,不需要显式地创建和销毁

6.1.10 taco_sys_mmz_alloc

描述

从 MMZ 内存区中申请一块内存。

详情

通过本接口申请的内存可以用作承载流式数据的环形缓冲区,以及任何用户认为合适的用途。

语法

taco_s32 taco_sys_mmz_alloc(
taco_u64 *phys_addr,
const taco_char *mmb,
const taco_char *zone_name,
taco_u32 len
);

参数说明

参数名称描述输入/输出
phys_addr申请的内存区域的物理地址输出
mmb给申请的内存区域取的名字,若为 NULL,则名字为 null,最大长度 32 bytes输入
zone_name申请的内存区域的 zone 的名字输入
len申请的内存区域的长度输入

返回值

返回值描述
0成功
非 0失败

注意事项

  • 为了控制内存碎片化风险,不宜频繁申请释放 MMB

6.1.11 taco_sys_mmz_free

描述

释放一个 MMB 内存块。

语法

taco_s32 taco_sys_mmz_free(taco_u64 phys_addr);

参数说明

参数名称描述输入/输出
phys_addr要释放的 MMB 内存块的物理地址输入

返回值

返回值描述
0成功
非 0失败,返回错误码

注意事项

  • 为了控制内存碎片化风险,不宜频繁申请释放 MMB

6.1.12 taco_sys_mmap_noncache

描述

映射一个物理地址,获得虚拟地址,类型为不可缓存。

语法

taco_void * taco_sys_mmap_noncache(taco_u64 phys_addr, taco_u32 size);

参数说明

参数名称描述输入/输出
phys_addr需要映射的物理地址输入
size需要映射的物理地址区域大小输入

返回值

返回值描述
NULL成功
NULLmmap 失败,提示错误信息

6.1.13 taco_sys_mmap_cache

描述

映射一个物理地址,获得虚拟地址,类型为可缓存。

语法

taco_void * taco_sys_mmap_cache(taco_u64 phys_addr, taco_u32 size);

参数说明

参数名称描述输入/输出
phys_addr需要映射的物理地址输入
size需要映射的物理地址区域大小输入

返回值

返回值描述
NULL成功
NULLmmap 失败,提示错误信息

6.1.14 taco_sys_munmap

描述

解除给定虚拟地址的映射关系。

语法

taco_s32 taco_sys_munmap(taco_void *virt_addr, taco_u32 size);

参数说明

参数名称描述输入/输出
virt_addr需要解除映射的虚拟地址输入
size需要解除映射的虚拟地址区域的大小输入

返回值

返回值描述
0成功
TACO_ERR_ILLEGAL_PARAM失败,虚拟地址 virt_addr 无效,提示错误信息
TACO_ERR_UNEXIST失败,munmap 失败,提示错误信息

6.1.15 taco_sys_cache_invalidate

描述

将 cache 内容标记为无效。

语法

taco_s32 taco_sys_cache_invalidate(taco_void *virt_addr, taco_u32 size);

参数说明

参数名称描述输入/输出
virt_addr虚拟地址输入
size虚拟地址指向空间的内存大小输入

返回值

返回值描述
0成功
非 0失败

6.1.16 taco_sys_cache_flush

描述

将 cache 中缓存的数据写入主内存。

语法

taco_s32 taco_sys_cache_flush(taco_void *virt_addr, taco_u32 size);

参数说明

参数名称描述输入/输出
virt_addr虚拟地址输入
size虚拟地址指向空间的内存大小输入

返回值

返回值描述
0成功
非 0失败

6.1.17 使用示例

对于开发者而言,常用的接口主要是申请 block 内存,获取物理地址,获取虚拟地址。接口文件包含在 taco_sys_api.h 中,链接库名为 libtacosys.so

#include <stdio.h>
#include <stdlib.h>
#include "taco_sys_api.h"

int main()
{
// tasys 初始化
taco_sys_init();

int total_size_in = 640 * 640 * 1.5;

// 申请 block 内存,从公共缓存池或指定缓存池中申请一个缓存块
// TACO_INVALID_POOLID 为特殊值,表示从公共缓存池中申请
// "anonymous" 为申请的内存区域的 zone 的名字
unsigned int blk_id_in = taco_sys_get_block(TACO_INVALID_POOLID, total_size_in, "anonymous");

// 通过 block ID 获取物理地址
unsigned long long physAddr_in = taco_sys_handle2_phys_addr(blk_id_in);

// 通过物理地址获取虚拟地址,为 uncache 的内存
unsigned char* data_in = (unsigned char*)taco_sys_mmap_noncache(physAddr_in, total_size_in);

// 释放虚拟地址,解除映射关系
taco_sys_munmap(data_in, total_size_in);

// 归还 block 至缓存池,注意:释放 blk 之前请解除映射关系
taco_sys_release_block(blk_id_in);

// 如果不想从缓存池申请内存,也可以通过 mmz_alloc 申请物理内存
// "mmb" 是给申请的内存区域取的名字
taco_sys_mmz_alloc(&physAddr_in, "mmb", "anonymous", total_size_in);

return 0;
}

6.2 taCV 接口详解

模块提供的所有接口都是同步接口,用户在调用接口时需要同时提供输入输出 buffer,如果接口返回成功,则输出 buffer 中已含有输出图像。接口依赖 tasys 模块提供帧缓存,用户在创建公共缓存池时,应为本模块预留合适大小和数量的帧缓存。taCV 提供图像处理 SPP 硬件加速接口,可以对图像做 crop、resize 和格式转换的操作。

6.2.1 ta_cv_image_resize

描述

实现对图像的 resize 等操作,只支持 down scale。

语法

tacv_status_t ta_cv_image_resize(
ta_cv_resize_image_t resize_attr,
ta_image_t input,
ta_image_t output);

参数说明

参数名称描述输入/输出
resize_attrresize 图像信息输入
input输入图像信息输入
output输出图像信息输出

返回值

返回值描述
0成功
非 0失败

格式支持

NumInput_Image_FormatOutput_Image_Format
1FORMAT_NV12FORMAT_NV12

注意事项

  • 最大缩放比为 128,最大输入输出分辨率为 4096×2160
  • 缩放(resize)操作只支持缩小
  • crop_width >= resize_width
  • 宽/高需为 16 的倍数

6.2.2 ta_cv_image_crop

描述

实现对图像的 crop 操作。

语法

tacv_status_t ta_cv_image_crop(
int crop_num,
ta_cv_rect_t* rects,
ta_image_t input,
ta_image_t* output);

参数说明

参数名称描述输入/输出
crop_num需要 crop 的数量输入
rectscrop 信息指针输入
input输入图像信息输入
output输出图像信息指针输出

返回值

返回值描述
0成功
非 0失败

格式支持

NumInput_Image_FormatOutput_Image_Format
1FORMAT_NV12FORMAT_NV12

注意事项

  • 最大输入输出分辨率为 4096×2160
  • crop_widthcrop_height 必须为偶数
  • 要确保裁剪区域不会超出原始图像的右边界(水平方向)和下边界(垂直方向)
  • 宽/高需为 16 的倍数

6.2.3 ta_cv_yuv2bgr_ext

描述

实现 YUV 格式到 RGB 格式的转换。

语法

ta_status_t ta_cv_yuv2bgr_ext(
int image_num,
ta_image_t* input,
ta_image_t* output,
ta_hw_select_t hw_select);

参数说明

参数名称描述输入/输出
image_num输入图片数量输入
input输入图片结构体指针输入
output输出图片结构体指针输出
hw_select选择执行的硬件输入

返回值

返回值描述
0成功
非 0失败

格式支持

NumInput_Image_FormatOutput_Image_Format
1FORMAT_NV12FORMAT_BGR_PLANAR
2FORMAT_NV12FORMAT_RGB_PLANAR
3FORMAT_NV12FORMAT_RGB_PACKED
4FORMAT_NV12FORMAT_BGR_PACKED

注意事项

  • 所有输入图像的 image_formatdata_typewidthheight 必须一致
  • 所有输出图像的 image_formatdata_typewidthheight 必须一致
  • 输出图像的 widthheight 必须与输入图像一致

6.2.4 ta_cv_image_csc_convert_to

描述

实现对图像的 crop + resize + csc 等操作。

语法

tacv_status_t ta_cv_image_csc_convert_to(
ta_image_t input,
ta_image_t output,
ta_cv_rect_t crop_rect,
ta_cv_resize_image_t* resize,
csc_type_t csc_typ);

参数说明

参数名称描述输入/输出
input输入图像信息输入
output输出图像信息输出
crop_rectcrop 参数输入
resizeresize 图像的参数指针输入
csc_typ颜色空间转换类型输入

返回值

返回值描述
0成功
非 0失败

格式支持

NumInput_Image_FormatOutput_Image_Format
1FORMAT_NV12FORMAT_NV12
2FORMAT_NV12FORMAT_NV21
3FORMAT_NV12FORMAT_RGB_PACKED
4FORMAT_NV12FORMAT_BGR_PACKED
5FORMAT_NV12FORMAT_RGB_PLANAR
6FORMAT_NV12FORMAT_BGR_PLANAR
7FORMAT_NV12FORMAT_ABGR_PACKED
8FORMAT_NV12FORMAT_ARGB_PACKED

注意事项

  • 最大缩放比为 128,最大输入输出分辨率为 4096×2160
  • 缩放(resize)操作只支持缩小
  • crop_width >= resize_width
  • 宽/高需为 16 的倍数

6.2.5 ta_cv_image_jpeg_enc

描述

实现对图像进行 JPEG 编码操作。

语法

tacv_status_t ta_cv_image_jpeg_enc(
ta_image_t* src,
unsigned int jpeg_data_blk,
size_t* out_size,
int quality_factor);

参数说明

参数名称描述输入/输出
src输入图像指针输入
jpeg_data_blk输出 buffer 的 blk_id输入
out_size输出 buffer 的 size 指针输入/输出
quality_factor图像质量因子输入

返回值

返回值描述
0成功
非 0失败

格式支持

NumInput_Image_FormatOutput_Image_Format
1FORMAT_NV12
2FORMAT_YUV420P

注意事项

  • 申请输出 buffer 的大小要大于等于输入 buffer 的大小
  • 支持大小 96×32 到 8192×8192(宽×高)
  • widthheight 必须为偶数
  • 图像质量因子 quality_factor 的取值范围为 (0, 100]

6.2.6 ta_cv_image_jpeg_dec

描述

实现对 JPEG 图像进行解码操作。

语法

tacv_status_t ta_cv_image_jpeg_dec(
size_t in_size,
unsigned int jpeg_in_blk_id,
ta_image_t *dst);

参数说明

参数名称描述输入/输出
in_size输入图像 buffer 大小输入
jpeg_in_blk_id输入图像 block_id输入
dst输出图像信息指针输入/输出

返回值

返回值描述
0成功
非 0失败

格式支持

NumInput_Image_FormatOutput_Image_Format
1FORMAT_NV12
2FORMAT_NV21
3FORMAT_RGB_PACKED
4FORMAT_BGR_PACKED
5FORMAT_BGR_PLANAR
6FORMAT_RGB_PLANAR

注意事项

  • 最大输入输出分辨率 32768×32768
  • 宽/高需为 16 的倍数
  • 调用接口前需要创建输出图像
  • 调用接口前需要准备好输入输出 buffer

6.2.7 taCV 示例程序

#include "ta_cv_api_ext_c.h"
#include "taco_sys_api.h"
#include <stdio.h>
#include <string.h>

int main(int argc, const char** argv)
{
int ret = 0;
int width = atoi(argv[2]);
int height = atoi(argv[3]);
int out_width = atoi(argv[4]);
int out_height = atoi(argv[5]);
int format = FORMAT_NV12;
int total_size_in = width * height * 1.5;
int total_size_out = out_width * out_height * 1.5;

total_size_in = SAMPLE_ALIGN(4096, total_size_in);
total_size_out = SAMPLE_ALIGN(4096, total_size_out);

unsigned long long physAddr_in = 0;
unsigned long long physAddr_out = 0;

// 初始化 tasys,获取 block
taco_sys_init();
ta_avframe_t frame_in[1], frame_out[1];

unsigned int blk_id_in = taco_sys_get_block(0xffffffff, total_size_in, "anonymous");
char str_blk_id_in[16];
physAddr_in = taco_sys_handle2_phys_addr(blk_id_in);
unsigned char* data_in = (unsigned char*)taco_sys_mmap_noncache(physAddr_in, total_size_in);
sprintf(str_blk_id_in, "%u", blk_id_in);

/* 填充输入 av_frame */
TA_AVDictionaryEntry elems;
elems.value = str_blk_id_in;
TA_AVDictionary metadata_in;
metadata_in.elems = &elems;

frame_in[0].data[0] = data_in;
frame_in[0].metadata = &metadata_in;
frame_in[0].width = width;
frame_in[0].height = height;
frame_in[0].format = TA_AV_PIX_FMT_NV12;

/* 填充输出 av_frame */
char str_blk_id_out[16];
unsigned int blk_id_out = taco_sys_get_block(0xffffffff, total_size_out, "anonymous");
physAddr_out = taco_sys_handle2_phys_addr(blk_id_out);
unsigned char* data_out = (unsigned char*)taco_sys_mmap_noncache(physAddr_out, total_size_out);

sprintf(str_blk_id_out, "%u", blk_id_out);
TA_AVDictionaryEntry elems_out;
elems_out.value = str_blk_id_out;
TA_AVDictionary metadata_out;
metadata_out.elems = &elems_out;
frame_out[0].data[0] = data_out;
frame_out[0].metadata = &metadata_out;
frame_out[0].width = out_width;
frame_out[0].height = out_height;
frame_out[0].format = TA_AV_PIX_FMT_NV12;

FILE *fd = fopen(argv[1], "rb");
fread(data_in, total_size_in, 1, fd);
fclose(fd);

// 创建图像结构体
ta_image_t image_in, image_out;
ta_cv_image_create(height, width, (ta_image_format_ext_t)format, DATA_TYPE_EXT_1N_BYTE, &image_in, (ta_avframe_t*)&frame_in[0]);
ta_cv_image_create(out_height, out_width, (ta_image_format_ext_t)format, DATA_TYPE_EXT_1N_BYTE, &image_out, (ta_avframe_t*)&frame_out[0]);

ta_cv_resize_image_t resize_attr = {0};
memset(&resize_attr, 0, sizeof(ta_cv_resize_image_t));
ta_cv_resize_t resize = {0};
resize.in_height = height;
resize.in_width = width;
resize.out_height = out_height;
resize.out_width = out_width;
resize.start_x = 0;
resize.start_y = 0;
resize_attr.resize_img_attr = &resize;
resize_attr.interpolation = 3;

// 调用函数
ret = ta_cv_image_resize(&resize_attr, image_in, image_out);

fd = fopen("resize_output.bin", "wb");
fwrite(data_out, total_size_out, 1, fd);
fclose(fd);

// 释放 block
taco_sys_munmap(data_in, total_size_in);
taco_sys_release_block(blk_id_in);
taco_sys_munmap(data_out, total_size_out);
taco_sys_release_block(blk_id_out);

ta_cv_image_destroy(&image_in);
ta_cv_image_destroy(&image_out);

return ret;
}

6.3 taRuntime 接口详解

6.3.1 ta_runtime_init

描述

实现模块初始化流程,为后续模型加载与推理运行做好软硬件准备。

详情

该接口完成硬件和软件相关资源的初始化操作。主要包括初始化 NPU 硬件资源和驱动程序。 本函数应在其他接口调用前执行,每个进程仅需调用一次,且需要与 ta_runtime_deinit 接口配对使用。若未调用该接口即尝试加载模型或进行推理,相关接口会返回失败。

语法

taco_status_t ta_runtime_init();

返回值

错误码描述
0成功
非 0失败

注意事项

  • 支持多进程、多线程,每个进程都应调用一次,最先调用的生效
  • 每个进程仅调用一次即可,不应每个线程都调用

6.3.2 ta_runtime_deinit

描述

实现模块反初始化流程,包括释放已分配的各种资源,关闭 NPU 服务。

详情

本接口用于在应用程序退出前对各种资源进行清理,释放初始化和运行阶段所申请的资源。

语法

taco_status_t ta_runtime_deinit();

返回值

错误码描述
0成功
非 0失败

注意事项

  • 支持多进程、多线程,每个进程都应调用一次,最后调用的生效
  • 每个进程仅调用一次即可,不应每个线程都调用

6.3.3 ta_runtime_load_model_from_file

描述

从文件系统中读取模型文件,解析文件信息并创建可在板端运行的网络模型。

详情

接口从文件系统中读取的是 NB 格式的模型文件,加载到系统域内存区。接口内部对 NB 文件进行解析,提取出 NPU 推理所需的指令流和权重数据,保存在 NN 域内存区。文件解析完毕后,系统域的输入数据就不再需要了,用户可以释放该 buffer。

语法

taco_status_t ta_runtime_load_model_from_file(
ta_runtime_context *context,
const char *model_path,
uint32_t core_index);

参数说明

参数描述输入/输出
contextta_runtime_context 类型的结构体指针。该结构体由 SDK 内部逻辑维护,用户需要在相关接口中传递该指针,除此之外无需使用该结构体输入/输出
model_path模型路径输入
core_indexNPU 设备支持两个 cluster,编号为 0 和 1。此参数用于指定模型部署至哪个 cluster 上运行。若模型类型为 dual-core,则该参数必须设置为 0输入

返回值

错误码描述
0成功
非 0失败

注意事项

  • 确保在调用该接口前某个进程执行了模块初始化操作

6.3.4 ta_runtime_load_model_at_ddr

描述

从 DDR 内存中读取模型信息,解析并创建可在板端运行的网络。

详情

接口从系统域输入 buffer 读取的是 NB 格式的模型信息,接口内部对 NB 信息进行解析,提取出 NPU 推理所需的指令流和权重数据,保存在 NN 域内存区。解析完成后,系统域输入 buffer 就不再需要了,用户可以释放该 buffer。

语法

taco_status_t ta_runtime_load_model_at_ddr(
ta_runtime_context *context,
void* model,
const uint64_t model_size,
uint32_t core_index);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
model模型数据指针输入
model_size模型尺寸输入
core_indexta_runtime_load_model_from_file输入

返回值

错误码描述
0成功
非 0失败

注意事项

  • 确保在调用该接口前某个进程执行了模块初始化操作

6.3.5 ta_runtime_query

描述

查询模型输入输出信息、模型推理的总时间,以及模型相关信息。

语法

taco_status_t ta_runtime_query(
ta_runtime_context *context,
const uint32_t property,
void *value);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
property查询指令输入
value存放返回结果的 buffer 地址输入/输出

返回值

错误码描述
0成功
非 0失败

查询命令

查询命令描述返回值类型
TACONN_QUERY_DRIVER_VERSION查询驱动版本uint32_t
TACONN_QUERY_IN_OUT_NUM查询输入输出 tensor 个数taconn_input_ouput_num_t
TACONN_QUERY_INPUT_ATTR查询输入 tensor 属性taconn_inout_attr_t
TACONN_QUERY_OUTPUT_ATTR查询输出 tensor 属性taconn_inout_attr_t
TACONN_QUERY_LAYER_COUNT查询网络模型总层数uint32_t
TACONN_QUERY_NETWORK_NAME查询网络名称char[]
TACONN_QUERY_PROFILING查询模型推理性能数据taconn_profile_t
TACONN_NETWORK_MEMORY_POOL_SIZE查询模型占用的 video_memory 内存大小taconn_memory_size_t

6.3.6 ta_runtime_set_input_cva

描述

用于设置模型的输入数据(图像或张量),输入地址类型为 CPU 虚拟地址,支持拷贝和映射两种访问方式。

详情

所谓输入数据,具体是指模型的第一层算子所需的输入数据,它的具体形式取决于模型的要求。多数模型需要一幅图像作为输入,有些模型可能需要两幅或者更多图像。而图像格式可以有 NV12、RGB、Tensor 等多种选项,图像的数据精度一般是 INT8。 该接口支持一次设置多个输入,因此用户需要提供一个 taconn_input_t 结构体的数组,并且确保结构体的所有参数均已正确赋值,未使用的参数应清零。 如果使用拷贝方式,本接口会在 NN 域申请一个 buffer(涉及存储空间+虚拟地址两种资源),将输入数据拷贝到 NN 域 buffer,所以接口返回后输入 buffer 可以立即释放。NN 域 buffer 会在推理结束后由 SDK 自动释放。 如果使用映射方式,本接口会在 NN 域申请一段虚拟地址,并与输入数据所在的内存页面建立映射关系。接口返回后输入 buffer 不能立即释放,必须等推理结束后才能释放。NN 域虚拟地址会在推理结束后由 SDK 自动释放。

语法

taco_status_t ta_runtime_set_input_cva(
ta_runtime_context *context,
uint32_t input_num,
taconn_input_t *input);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
input_num模型输入的个数输入
input指针,指向一个 taconn_input_t 类型的数组输入

返回值

错误码描述
0成功
非 0失败

注意事项

  • 结构体在赋值前应整体清零,在参数有误的情况下,清零有利于故障现象的一致性
  • 输入数量不应超过模型所需的输入个数,否则接口会报错
  • 输入数据的地址必须是 256 对齐(地址指针的低 8 位全为 0),否则接口会报错

6.3.7 ta_runtime_set_input_pha

描述

用于设置模型的输入数据,输入地址类型为物理地址。

详情

本接口内部将输入的物理地址映射为 NPU 虚拟地址,一次推理结束后,接口内部会尝试把虚拟地址缓存到内部查找表中,待模块卸载时统一释放。 该接口支持多个输入,因此用户需要提供一个 taconn_input_phy_t 结构体的数组,并且确保结构体的所有参数均已正确赋值,未使用的参数应清零。 本接口内部在 NN 域申请一段虚拟地址,并与输入数据所在的内存页面建立映射关系。接口返回后输入 buffer 不能立即释放,必须等推理结束后才能释放。NN 域虚拟地址会优先缓存在接口内部的查找表中,待模块销毁时由 SDK 自动释放;如果未能缓存到查找表则会立即释放。

语法

taco_status_t ta_runtime_set_input_pha(
ta_runtime_context *context,
uint32_t input_num,
taconn_input_phy_t *input);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
input_num模型输入的个数输入
input指向 taconn_input_phy_t 类型结构体数组。每个元素代表一个输入的物理地址段信息,包括物理地址表和对应大小表输入

返回值

错误码描述
0成功
非 0失败

注意事项

  • 用户应在开始推理前完成输入 buffer 的设置,如果设置不全,推理接口会报错
  • 本接口允许用户针对同一目标通道多次设置输入 buffer,旧的设置自动失效
  • 结构体在赋值前应整体清零,在参数有误的情况下,清零有利于故障现象的一致性
  • 输入数量不应超过模型所需的输入个数,否则接口会报错
  • 输入数据的地址必须是 256 对齐(地址指针的低 8 位全为 0),否则接口会报错

6.3.8 ta_runtime_create_buffer

描述

用于在 NN 域创建一个保存推理输出结果的缓冲区。

详情

本接口与 ta_runtime_set_output() 接口配合使用,作为该接口的前序接口,用于准备模型输出 buffer。 用户在调用本接口时,仅需传入所需 buffer 的大小,接口内部会自动分配内存并填充 taconn_buffer_t 结构体内容,包括数据指针、buffer size 等信息。结构体 data 字段指向的地址是一个可供 CPU 访问的虚拟地址指针,用户可通过该指针读取推理输出结果。

语法

taco_status_t ta_runtime_create_buffer(
ta_runtime_context *context,
uint32_t size,
taconn_buffer_t *buffer);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
size需要创建的 buffer 大小输入
buffer指针,指向一个 taconn_buffer_t 结构体输出

返回值

错误码描述
0成功
非 0失败

注意事项

  • 用户需要根据模型情况计算 buffer 大小,如果 buffer 不够大,后序接口会失败
  • 本接口应与 ta_runtime_destroy_buffer() 接口成对使用

6.3.9 ta_runtime_destroy_buffer

描述

销毁由 ta_runtime_create_buffer() 创建的 NN 域 buffer,并释放对应的 CPU 虚拟地址资源。

语法

taco_status_t ta_runtime_destroy_buffer(
ta_runtime_context *context,
taconn_buffer_t *buffer);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
buffer指向待销毁的 taconn_buffer_t 类型结构体。该结构体需由 ta_runtime_create_buffer() 创建,函数调用后其内部数据指针即失效输入&输出

返回值

错误码描述
0成功
非 0失败

注意事项

  • 本接口应与 ta_runtime_create_buffer() 接口成对使用
  • 用户程序应在销毁前停止访问 taconn_buffer_t 的成员变量
  • 应避免多次调用销毁同一 buffer 结构体,或销毁未初始化的 buffer,否则产生 UB 行为

6.3.10 ta_runtime_set_output

描述

设置模型推理的输出 buffer。

详情

本接口为模型的指定输出通道设置一个 NN 域输出 buffer,模型推理结束后,用户通过 NN 域 buffer 对应的 CPU 虚拟地址读取推理结果。 本接口与 ta_runtime_create_buffer() 接口配合使用,作为该接口的后序接口。

语法

taco_status_t ta_runtime_set_output(
ta_runtime_context *context,
uint32_t output_num,
taconn_buffer_t *buffer);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
output_num模型的输出个数输入
buffertaconn_buffer_t 结构体指针输入

返回值

错误码描述
0成功
非 0失败

注意事项

  • 用户应在开始推理前设置输出 buffer,否则推理接口会报错

6.3.11 ta_runtime_invalidate_buffer

描述

将 CPU cache 中与 NN 域 buffer 对应的虚拟地址标记为 invalid,确保下次会从 DDR 中读取数据。

详情

NPU 完成推理后,用户程序读取推理结果前需调用本接口,确保 CPU 能够读取到 DDR 中的最新数据,而不是从缓存中读取旧数据。

语法

taco_status_t ta_runtime_invalidate_buffer(
ta_runtime_context *context,
taconn_buffer_t *buffer);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入
buffer指向 taconn_buffer_t 类型结构体的指针,表示待刷新缓存的一块 NN 域缓冲区。该结构体应由 ta_runtime_create_buffer() 创建并合法初始化输入

返回值

错误码描述
0成功
非 0失败

6.3.12 ta_runtime_run_network

描述

执行一次模型推理。

详情

在调用本接口进行推理前,需要先设置好模型的输入输出 buffer。

语法

taco_status_t ta_runtime_run_network(ta_runtime_context *context);

参数说明

参数描述输入/输出
contextta_runtime_load_model_from_file输入

返回值

错误码描述
0成功
非 0失败

6.3.13 ta_runtime_destroy_context

描述

销毁 NNRT 上下文对象,并释放其关联的所有资源。

详情

该接口用于释放上下文对象 ta_runtime_context 及其内部管理的所有资源。 调用后,传入的 context 指针将被置为 0,表示已无效,不可再被用于任何 NNRT 操作。

语法

taco_status_t ta_runtime_destroy_context(ta_runtime_context *context);

参数说明

参数描述输入/输出
context指向要销毁的 ta_runtime_context 结构体指针输入/输出

返回值

错误码描述
0成功
非 0失败

6.4 taOpenCV 接口说明

TACO SDK 提供的 taOpenCV 库是在开源社区版本的基础上对部分常用算法实现了硬件加速,具体来说就是基于玄铁 C920 CPU 的 RVV 扩展指令集对图像缩放、插值滤波、颜色空间变换、通道分离合并、二值化、LK 光流、金字塔等常用算子算法进行了向量加速优化。

TACO SDK 中提供的 taOpenCV 相关版本信息如下。

OpenCV 版本OS 版本CPU 版本RVV 版本
4.5.4Linux 6.6玄铁 C920V21.0

关于 OpenCV 库的使用说明可参考 「OpenCV 官方网站」,关于 RISC-V RVV 的版本差异情况可参考 「RISC-V 官方 GitHub」

6.4.1 taOpenCV API 功能扩展

OpenCV 原生支持的一些 API 函数,如 imread()imwrite()imdecode()imencode() 等,可以自动识别 JPEG 格式并进行编解码处理。SDK 对这些 API 函数进行了扩展,使其能够自动选择合适的芯片硬件来完成任务。

此外,OpenCV 原生的 imread()imdecode() 函数在完成 JPEG 解码后返回 BGR packed 格式的图像,而 SDK 扩展了这些接口的行为,使其能够返回 YUV 和 RGB 格式图像。具体地:

  • 当接口配置成返回 YUV 时,解码器会根据 JPEG 文件头中提供的颜色通道数和 YUV 采样率确定输出 YUV 图像的具体格式(支持 I400、NV12、NV16)
  • 当接口配置成返回 RGB 时,解码器会直接把 YUV 转成用户设置的 RGB 格式输出(支持 Packed、Planar)。值得说明的是,从 YUV 到 RGB 的转换是由解码器内部的后处理单元完成的,没有额外的延迟和 DDR 带宽开销

除此之外,还有多个类别的接口已经支持扩展的 YUV 格式,包括:

  • 部分 Mat 类的成员函数,如 create()release()clone()
  • 部分 VideoCapture 类的成员函数,如 read()grab()
  • 部分 VideoWriter 类的成员函数,如 write() 接口
  • 部分图像处理类接口,如 cvtColor()resize()
  • 部分 2D 绘图类接口,如 line()rectangle()circle()putText()
Mat(AVFrame *frame)

描述 通过 AVFrame 创建 Mat 对象。 参数说明

参数描述输入/输出
frame与ffmpeg 的 AVFrame 对象对应。输入

返回值 返回Mat 对象。

imread( const String& filename, int flags = IMREAD_COLOR )

描述 对图片进行解码操作,taopencv对jpeg解码进行扩展,默认使用硬件进行jpeg解码出BGR数据格式,用户可通过修改flag为IMREAD_COLOR_YUV输出NV12格式,添加IMREAD_RETRY_SOFTDEC即取消硬件加速。

参数说明

参数描述输入/输出
filename输入的文件名输入
flags输入的标志位输入

返回值 返回Mat 对象。 注意 如果使用硬件解码jpeg图像,返回的Mat对象内存为tasys分配的内存块

imwrite( const String& filename, InputArray img,const std::vector<int>& params = std::vector<int>());

描述 对Mat进行编码操作,taopencv对jpeg编码进行扩展,支持NV12数据编码为jpeg。我们对params参数进行,可取消硬件加速。

vector<int> params;
params.push_back(cv::IMWRITE_JPEG_HARDWARE); // 取消硬件加速
params.push_back(0);

params.push_back(cv::IMWRITE_JPEG_SAMPLING_FACTOR); // 指定为NV12格式
params.push_back(cv::IMWRITE_JPEG_SAMPLING_FACTOR_NV12);

参数说明

参数描述输入/输出
filename输入的文件名输入
img输入的mat输入
params编码参数输入

返回值 返回Mat 对象。 注意 如果使用硬件编码jpeg图像,Mat对象内存必须为tasys分配的内存块

6.4.2 RVV 加速接口

TACO SDK 提供的 taOpenCV 库对部分接口进行了优化,其中,有些接口是使用了 RISC-V RVV 向量指令集实现的加速,下表对此类接口进行了汇总。

优化算子支持数据类型参数说明
addu8/s8/u16/s16/s32/f32/f64两个数组逐个元素做加运算
subu8/s8/u16/s16/s32/f32/f64两个数组逐个元素做减运算
maxu8/s8/u16/s16/s32/f32/f64两个数组逐个元素求最大值
minu8/s8/u16/s16/s32/f32/f64两个数组逐个元素求最小值
mulu8/s8/u16/s16/s32/f32/f64两个数组逐个元素做乘法运算
absdiffu8/s8/u16/s16/s32/f32/f64两个数组差值的绝对值(求帧差)
divu8/s8/u16/s16/s32/f32/f64两个数组逐个元素做除法运算
recipu8/s8/u16/s16/s32/f32/f64数组元素的倒数运算
addWeightedu8/s8/u16/s16/s32/f32/f64两个数组逐个元素做加权相加运算(alpha 运算)
and/or/xor/notu8按位做逻辑操作(与/或/异或/非)
cmpu8/s8/u16/s16/s32/f32/f64数组元素比较运算
splitu8/s8/u16/s32/s64将一个多通道数组分割成多个单通道数组
mergeu8/s8/u16/s32/s64将几个单通道数组合并成一个多通道数组
fastAtanf32/f64快速计算反正切值
BoxFilteru83x3, cn=1, norm
Resizeu8INTER_LINEAR, Area, Nearest
Thresholdu8/s8/u16/s16/f32/f64图像阈值化
Sobelu8->s16, u8->f32Sobel 边缘检测算子,3x3, cn=1; 5x5, cn=1
MedianBluru83x3, 5x5
BGRtoBGRu8bgr/bgra/rgb/rgba
BGRtoBGR5x5u8bgr/bgra/rgb/rgba->bgr565/bgr555
BGR5x5toBGRu8bgr565/bgr555->bgr/bgra/rgb/rgba
BGRtoGrayu8bgr/bgra/rgb/rgba->gray
GraytoBGRu8gray->bgr/bgra/rgb/rgba
BGRtoYUVu8bgr/bgra/rgb/rgba->YUV Planar
YUVtoBGRu8YUV Planar->bgr/bgra/rgb/rgba
BGRtoXYZu8bgr/bgra/rgb/rgba->XYZ
XYZtoBGRu8XYZ->bgr/bgra/rgb/rgba
TwoPlaneYUVtoBGRu8YUV Semi-Planar (NV12/NV21/etc.)
ThreePlaneYUVtoBGRu8YUV Planar (YUV420P/etc.)
BGRtoThreePlaneYUVu8YUV Planar (YUV420P/etc.)
BGRtoTwoPlaneYUVu8YUV Semi-Planar (NV12/NV21/etc.)
OnePlaneYUVtoBGRu8单平面 YUV 转 BGR
Dilateu83x3, cn=1,4; 4x4, cn=1; 5x5, cn=1; 15x15, cn=1
Erodeu83x3, cn=1,4; 4x4, cn=1; 5x5, cn=1; 15x15, cn=1
WarpAffineu8INTER_LINEAR (BORDER_REPLIATE/CONSTANT) NEAREST (BORDER_REPLIATE/CONSTANT)
WarpPrespectiveu8INTER_LINEAR (BORDER_REPLIATE/CONSTANT)
GaussianBluru87x7, cn=1
PyrDownu8BORDER_CONSTANT, cn=1/2/3/4
OptFlowPyrLKu8光流金字塔 LK 算法
countNTaonZerou8cn=1
convertu8/s8/u16/s16/s32/f32/f64数据类型转换
norm1u8L2, no mask
minMaxLof32max_val, no mask
calcMinEigenValf32计算最小特征值
calcHarrisf32Harris 角点检测

6.4.3 taOpenCV 示例程序

#include "opencv2/opencv.hpp"
#include <iostream>

cv::Mat image, scaled;

static void ta_convertRGB2NV12(Mat &src, Mat &dst) {

int cropWidth = src.cols / 2 * 2;
int cropHeight = src.rows / 2 * 2;

cv::Mat cropImage = src(cv::Rect(0, 0, cropWidth, cropHeight));

// std::ofstream ofs;
// ofs.open(outputFilePath, std::ios::binary);

// 创建一个YUV图像来存储转换后的数据
cv::Mat yuvImage(cropImage.rows * 3 / 2, cropImage.cols, CV_8UC1,
cv::Scalar(0)); // Y分量
// cv::Mat uvImage(cropImage.rows *3/ 2, cropImage.cols, CV_8UC1,
// cv::Scalar(0)); // UV分量 (NV12)

// 进行BGR到YUV颜色空间转换
cv::cvtColor(src, yuvImage, cv::COLOR_BGR2YUV_I420);

memcpy(dst.data, yuvImage.data, cropImage.cols * cropImage.rows);

int yLen = cropImage.cols * cropImage.rows;
int uvLen = cropImage.cols * cropImage.rows / 4;
// 将UV分量(U和V)从I420格式提取并排列为NV12格式
for (int el = 0; el < uvLen; el++) {
dst.data[yLen + 2 * el] = yuvImage.data[yLen + el];
dst.data[yLen + 2 * el + 1] = yuvImage.data[yLen + el + uvLen];
}

return;
}

int main( int argc, const char** argv )
{
std::string filename = "./fruits.jpg";
image = cv::imread(filename , cv::IMREAD_COLOR | cv::IMREAD_RETRY_SOFTDEC);
//error handling skipped
Mat image_nv12;
image_nv12.allocator = hal::getAllocator();
image_nv12.create(image.rows * 3 /2,image.cols,CV_8UC1);
ta_convertRGB2NV12(image, image_nv12);//convert to nv12

cv::resize(image_nv12, scaled, cv::Size(100,100), 0, 0, cv::INTER_LINEAR);
cv::imwrite("./output.jpg", scaled);

return 0;
}

6.5 taFFmpeg 接口说明

TACO SDK 提供的 taFFmpeg 基于 FFmpeg 官方的 4.3.2 版本,我们对 FFmpeg 进行了一些扩展,使其能够自动选择合适的芯片硬件来完成任务。前文已经对 taFFmpeg 有了一些描述,这个章节对支持的编解码器进行补充说明。

6.5.1 视频解码器

用户可通过如下命令来查询 taFFmpeg 支持的解码器。

ffmpeg -decoders

其结果中应包含由 TACO SDK 提供的硬件加速版 H.264 解码器,名称为 h264_taco。 用户可以通过如下命令行查询硬件解码器提供的一些额外选项:

ffmpeg -h decoder=h264_taco
ffmpeg -h decoder=hevc_taco

目前已经支持的选项有:

参数名称功能描述取值范围默认值
vdec_output_semi_planar指定输出图像的平面格式0 ~ 输出 YUV420 Planar 图像;1 ~ 输出 YUV420 Semi-planar 图像0
vdec_extra_frame_buffer_num额外提供的帧缓存数量大于等于 1 的整数2
vdec_stream_addr_typeBitstream 数据指针的类型0 ~ 物理地址,页面连续;1 ~ 虚拟地址,页面连续;2 ~ 虚拟地址,页面不保证连续0
vdec_fps_decimation解码后哪些帧需要写入 DDR0 ~ 全部写入 DDR;1 ~ 写一帧跳一帧;2 ~ 写一帧跳两帧0

这些选项可以使用 taFFmpeg 提供的 av_dict_set() 接口进行设置。

6.5.2 视频编码器

用户可通过如下命令来查询 taFFmpeg 支持的编码器。

ffmpeg -encoders

其结果中应包含由 TACO SDK 提供的硬件加速版 H.264 编码器,名称为 h264_taco。 用户可以通过如下命令行查询硬件编码器提供的一些额外选项:

ffmpeg -h encoder=h264_taco

目前已经支持的选项有:

参数名称功能描述取值范围默认值
venc_quality_mode指定编码的质量模式0 ~ 速度优先,质量低;1 ~ 均衡模式;2 ~ 质量优先,速度低2
venc_gop_size设置一个 GOP 包含的帧数大于等于 1 的整数30
venc_rc_mode码率控制算法0 ~ fixed qp;1 ~ vbr;2 ~ cbr2
venc_yuv_addr_typeYUV 数据指针的类型0 ~ 物理地址,页面连续;1 ~ 虚拟地址,页面连续;2 ~ 虚拟地址,页面不保证连续0

这些选项可以使用 taFFmpeg 提供的 av_dict_set() 接口进行设置。

6.5.3 JPEG 解码器

用户可以通过如下命令行查询硬件 JPEG 解码器是否已安装:

ffmpeg -decoders | grep jpeg_taco

用户可以通过如下命令行查询 JPEG 硬件解码器提供的一些额外选项:

ffmpeg -h decoder=jpeg_taco

目前已经支持的选项有:

参数名称功能描述取值范围默认值
jdec_bs_buffer_size设置输入流缓冲区的大小大于 0 的整数2
jdec_extra_frame_buffer_num额外提供的帧缓存数量大于等于 0 的整数,建议:Jpeg 可以为 0,mjpeg 大于 02
jdec_stream_addr_typeBitstream 数据指针的类型0 ~ 物理地址,页面连续;1 ~ 虚拟地址,页面连续;2 ~ 虚拟地址,页面不保证连续0

这些选项可以使用 taFFmpeg 提供的 av_dict_set() 接口进行设置。

6.5.4 JPEG 编码器

用户可以通过如下命令行查询硬件编码器提供的一些额外选项:

ffmpeg -encoders | grep jpeg_taco

用户可以通过如下命令行查询 JPEG 硬件解码器提供的一些额外选项:

ffmpeg -h encoder=jpeg_taco

目前已经支持的选项有:

参数名称功能描述取值范围默认值
jenc_bs_buffer_size设置输出流缓冲区的大小大于 0 的整数500*1024
jenc_yuv_addr_typeYUV 数据指针的类型0 ~ 物理地址,页面连续;1 ~ 虚拟地址,页面连续;2 ~ 虚拟地址,页面不保证连续0

6.5.5 结构体定义

AVFrame 结构体的定义位于 libavutil/frame.h 中,它封装了一个视频帧的多种信息,包括图像数据(编码前或解码后的未压缩数据)、时间戳、像素格式、分辨率等。

下面是一些关键字段的介绍:

  • data: 指针数组,每个指针指向视频帧数据的一个颜色通道(数据平面)。例如,对于 ffmpeg 默认的 YUV420P 格式,data[0] 指向 Y 分量,data[1]data[2] 分别指向 U 和 V 分量
  • linesize: 数组,对于图像的每个颜色通道,记录它的一行数据在内存中实际占用的字节数。它的大小取决于像素格式以及数据对齐要求。而数据对齐要求一般是源于生成或者消费这帧图像的硬件的特性
  • format: 视频帧的像素格式(例如 AV_PIX_FMT_YUV420P
  • width, height: 视频帧的宽度和高度
  • pts, pkt_dts: 时间戳信息,用于表示帧的显示时间

在使用 taFFmpeg 进行视频处理时,通常会涉及到以下接口:

  1. 解码: 使用 avcodec_receive_frame() 接口从解码器获取解码后的视频帧
  2. 处理: 使用 sws_scale() 接口对 AVFrame 中的数据进行缩放、裁剪或格式转换等视频处理操作
  3. 编码: 使用 avcodec_send_frame() 接口将处理后的 AVFrame 帧编码为压缩格式
  4. 释放: 使用 av_frame_free() 释放 AVFrame 结构体占用的内存

AVPacket 是 taFFmpeg 中很重要的一个数据结构,其中 A 代表 Audio,V 代表 Video。AVPacket 用于保存解复用之后、解压缩之前的音视频数据,以及关于这些数据的一些附加信息(side data),例如,显示时间戳(pts)、解码时间戳(dts)、数据时长(duration)、所在流媒体的索引(stream_index)等。

在使用 AVPacket 时有几个重要事项需要注意:

  1. AVPacket 的本质是一个数据描述体,它本身并不随身携带媒体数据,而是通过 data 指针指向音视频数据的缓存位置。所以,当对 AVPacket 结构体进行复制的时候,它所描述的音视频数据并没有被复制
  2. AVPacket 结构体描述视频时,它通常只包含一个完整的 Frame,而音频则有可能包含多个 Frame
  3. 允许存在一种特殊的 AVPacket,它只含有附加信息(side data)而没有音视频数据(data)